# utils/image_utils.py

import os
import logging
from PIL import Image
from PyQt5.QtGui import QPixmap, QImage
from concurrent.futures import ProcessPoolExecutor
from PyQt5.QtCore import QObject, pyqtSignal

def process_thumbnail(image_path, thumbnail_size):
    """
    在子进程中处理图像，生成缩略图并返回图像数据。
    """
    try:
        with Image.open(image_path) as img:
            # 使用高质量的LANCZOS滤镜进行缩放
            img.thumbnail((thumbnail_size, thumbnail_size),
                          Image.Resampling.LANCZOS if hasattr(Image, 'Resampling') else Image.LANCZOS)
            img = img.convert('RGBA')
            data = img.tobytes("raw", "RGBA")
            return (image_path, img.size, data)
    except Exception as e:
        logging.error(f"处理缩略图失败：{image_path} - {e}")
        return (image_path, None, None)

class ImageUtils(QObject):
    thumbnail_ready = pyqtSignal(str, QPixmap)

    def __init__(self, thumbnail_size=200):
        super().__init__()
        self.thumbnail_size = thumbnail_size
        self.executor = ProcessPoolExecutor(max_workers=os.cpu_count() // 2 or 4)
        self.cache = {}
        self.futures = {}

    def generate_thumbnail(self, image_path):
        if image_path in self.cache:
            self.thumbnail_ready.emit(image_path, self.cache[image_path])
            logging.debug(f"缩略图缓存命中：{image_path}")
            return
        # 提交图像处理任务到进程池
        future = self.executor.submit(process_thumbnail, image_path, self.thumbnail_size)
        future.add_done_callback(self._on_thumbnail_done)
        self.futures[future] = image_path
        logging.debug(f"已提交缩略图处理任务：{image_path}")

    def _on_thumbnail_done(self, future):
        image_path, size, data = future.result()
        if data is not None and size is not None:
            # 在主线程中创建 QPixmap
            qimage = QImage(data, size[0], size[1], QImage.Format_RGBA8888)
            pixmap = QPixmap.fromImage(qimage)
            self.cache[image_path] = pixmap
            self.thumbnail_ready.emit(image_path, pixmap)
            logging.info(f"缩略图已生成：{image_path}")
        else:
            logging.error(f"缩略图生成失败：{image_path}")
        # 从 futures 字典中移除已完成的任务
        del self.futures[future]

    def shutdown(self):
        """关闭进程池，确保所有子进程被正确终止。"""
        self.executor.shutdown(wait=True)
        logging.info("图像处理工具已关闭。")
